package org.itboys.pay.weixin;

import org.apache.commons.lang3.StringUtils;
import org.itboys.commons.utils.encryption.Digests;
import org.itboys.commons.utils.random.RandomUtils;

/**
 * 微信支付 统一下单的实体类
 * 
 * @author huml
 * 
 */
public class Unifiedorder {
	public static final String URL = "https://api.mch.weixin.qq.com/pay/unifiedorder";// 统一下单的链接

	public static final String TRADE_TYPE_JS = "JSAPI";// H5调用
	public static final String TRADE_TYPE_SCAN = "NATIVE";// 扫描二维码调用
	public static final String TRADE_TYPE_APP = "APP";//APP支付

	private String appid;// 微信appid 必须
	private String body;// 商品或支付单简要描述 必须
	private String mchId;// 商户号 必须
	private String nonceStr;// 随机字符串 必须
	private String notifyUrl;// 异步回调地址 必须
	private String openid;// 用户的openid,仅当trade_type=JSAPI时，此参数必传，用户在商户appid下的唯一标识
	private String outTradeNo;// 商户系统内部的订单号,32个字符内、可包含字母 必须
	private String spbillCreateIp;// APP和网页支付提交用户端ip，Native支付填调用微信支付API的机器IP 必须
	private String totalFee;// 订单总金额,只能为整数 必须
	private String tradeType;// 交易类型 trade_type=JSAPI表示H5页面发起调用 必须
	private String sign;// 签名

	private String attach;// 说明 非必须
	private String deviceInfo;// 设备号 终端设备号(门店号或收银设备ID)，注意：PC网页或公众号内支付请传"WEB" 非必须
	private String detail;// 商品详情 非必须
	private String feeType;// 货币类型 默认人民币:CNY 非必须
	private String timeStart;// 订单生成时间，格式为yyyyMMddHHmmss 非必须
	private String timeExpire;// 订单失效时间，格式为yyyyMMddHHmmss 非必须
	private String goodsTag;// 商品标记，代金券或立减优惠功能的参数 非必需
	private String productId;// trade_type=NATIVE，此参数必传。此id为二维码中包含的商品ID，商户自行定义。
	
	private String key;//支付key 必须

	public Unifiedorder() {
	}
	/**
	 * 带参数的构造器
	 * @param openid  openid仅当trade_type=JSAPI时，此参数必传，用户在商户appid下的唯一标识
	 * @param outTradeNo  商户系统内部的订单号,32个字符内、可包含字母 必须
	 * @param spbillCreateIp  APP和网页支付提交用户端ip，Native支付填调用微信支付API的机器IP 必须
	 * @param tradeType  交易类型 trade_type=JSAPI表示H5页面发起调用 必须  JSAPI APP NATIVE
	 * @param body  商品或支付单简要描述 必须
	 * @param totalFee  订单总金额,只能为整数,单位为分 必须
	 * @param key  支付key 必须
	 */
	/*public Unifiedorder(String appid, String mchId,
			String openid, String outTradeNo,
			String spbillCreateIp, String tradeType, String body,
			String totalFee, String notifyUrl, String productId, String key) {
		this.appid = appid;
		this.mchId = mchId;
		this.openid = openid;
		this.outTradeNo = outTradeNo;
		this.spbillCreateIp = StringUtils.isNotBlank(spbillCreateIp) ? spbillCreateIp
				: "127.0.0.1";
		this.tradeType = tradeType;
		this.body = body;
		this.totalFee = totalFee;
		this.nonceStr = RandomUtils.getClearRandomStr(32);
		this.notifyUrl = notifyUrl;
		this.productId = productId;
		this.key = key;
	}*/
	public Unifiedorder(String appid, String mchId,
						String openid, String outTradeNo,
						String spbillCreateIp, String tradeType, String body,
						String totalFee, String notifyUrl, String key) {
		this.appid = appid;
		this.mchId = mchId;
		this.openid = openid;
		this.outTradeNo = outTradeNo;
		this.spbillCreateIp = StringUtils.isNotBlank(spbillCreateIp) ? spbillCreateIp
				: "127.0.0.1";
		this.tradeType = tradeType;
		this.body = body;
		this.totalFee = totalFee;
		this.nonceStr = RandomUtils.getClearRandomStr(32);
		this.notifyUrl = notifyUrl;

		this.key = key;
	}
	/**
	 * 完整的xml格式的参数 含签名
	 * 
	 * @return
	 */
	public String getXML() {
		String signStr = "appid=" + this.appid;
		String xml = "<xml>" + "<appid>" + this.appid + "</appid>";
		if (StringUtils.isNotBlank(this.attach)) {
			xml += "<attach>支付测试</attach>";
			signStr += "&attach=" + this.attach;
		}
		xml += "<body>" + this.body + "</body>";
		signStr += "&body=" + this.body;
		if (StringUtils.isNotBlank(this.detail)) {
			xml += "<detail>" + this.detail + "</detail>";
			signStr += "&detail=" + this.detail;
		}
		if (StringUtils.isNotBlank(this.deviceInfo)) {
			xml += "<device_info>" + this.deviceInfo + "</device_info>";
			signStr += "&device_info=" + this.deviceInfo;
		}
		if (StringUtils.isNotBlank(this.feeType)) {
			xml += "<fee_type>" + this.feeType + "</fee_type>";
			signStr += "&fee_type=" + this.feeType;
		}
		if (StringUtils.isNotBlank(this.goodsTag)) {
			xml += "<goods_tag>" + this.goodsTag + "</goods_tag>";
			signStr += "&goods_tag=" + this.goodsTag;
		}

		xml += "<mch_id>" + this.mchId + "</mch_id>" + "<nonce_str>"
				+ this.nonceStr + "</nonce_str>" + "<notify_url>"
				+ this.notifyUrl + "</notify_url>";
		signStr += "&mch_id=" + this.mchId + "&nonce_str=" + this.nonceStr
				+ "&notify_url=" + this.notifyUrl;
		if (StringUtils.isNotBlank(this.openid)) {
			xml += "<openid>" + this.openid + "</openid>";
			signStr += "&openid=" + this.openid;
		}
		xml += "<out_trade_no>" + this.outTradeNo + "</out_trade_no>";
		signStr += "&out_trade_no=" + this.outTradeNo;
		if (StringUtils.isNotBlank(this.productId)) {
			xml += "<product_id>" + this.productId + "</product_id>";
			signStr += "&product_id=" + this.productId;
		}
		xml += "<spbill_create_ip>" + this.spbillCreateIp
				+ "</spbill_create_ip>";
		if (StringUtils.isBlank(this.spbillCreateIp)) {
			signStr += "&spbill_create_ip=127.0.0.1";
		} else {
			signStr += "&spbill_create_ip=" + this.spbillCreateIp;
		}
		if (StringUtils.isNotBlank(this.timeExpire)) {
			xml += "<time_expire>" + this.timeExpire + "</time_expire>";
			signStr += "&time_expire=" + this.timeExpire;
		}
		if (StringUtils.isNotBlank(this.timeStart)) {
			xml += "<time_start>" + this.timeStart + "</time_start>";
			signStr += "&time_start=" + this.timeStart;
		}
		xml += "<total_fee>" + this.totalFee + "</total_fee>" + "<trade_type>"
				+ this.tradeType + "</trade_type>";
		signStr += "&total_fee=" + this.totalFee + "&trade_type="
				+ this.tradeType + "&key=" + key;

		signStr = Digests.md5(signStr);
		this.sign = signStr;
		xml += "<sign>" + signStr + "</sign>" + "</xml>";
		return xml;
	}

	public String getAppid() {
		return appid;
	}

	public void setAppid(String appid) {
		this.appid = appid;
	}

	public String getAttach() {
		return attach;
	}

	public void setAttach(String attach) {
		this.attach = attach;
	}

	public String getBody() {
		return body;
	}

	public void setBody(String body) {
		this.body = body;
	}

	public String getMchId() {
		return mchId;
	}

	public void setMchId(String mchId) {
		this.mchId = mchId;
	}

	public String getNonceStr() {
		return nonceStr;
	}

	public void setNonceStr(String nonceStr) {
		this.nonceStr = nonceStr;
	}

	public String getNotifyUrl() {
		return notifyUrl;
	}

	public void setNotifyUrl(String notifyUrl) {
		this.notifyUrl = notifyUrl;
	}

	public String getOpenid() {
		return openid;
	}

	public void setOpenid(String openid) {
		this.openid = openid;
	}

	public String getOutTradeNo() {
		return outTradeNo;
	}

	public void setOutTradeNo(String outTradeNo) {
		this.outTradeNo = outTradeNo;
	}

	public String getSpbillCreateIp() {
		return spbillCreateIp;
	}

	public void setSpbillCreateIp(String spbillCreateIp) {
		this.spbillCreateIp = spbillCreateIp;
	}

	public String getTotalFee() {
		return totalFee;
	}

	public void setTotalFee(String totalFee) {
		this.totalFee = totalFee;
	}

	public String getTradeType() {
		return tradeType;
	}

	public void setTradeType(String tradeType) {
		this.tradeType = tradeType;
	}

	public String getSign() {
		return sign;
	}

	public void setSign(String sign) {
		this.sign = sign;
	}

	public String getDeviceInfo() {
		return deviceInfo;
	}

	public void setDeviceInfo(String deviceInfo) {
		this.deviceInfo = deviceInfo;
	}

	public String getDetail() {
		return detail;
	}

	public void setDetail(String detail) {
		this.detail = detail;
	}

	public String getFeeType() {
		return feeType;
	}

	public void setFeeType(String feeType) {
		this.feeType = feeType;
	}

	public String getTimeStart() {
		return timeStart;
	}

	public void setTimeStart(String timeStart) {
		this.timeStart = timeStart;
	}

	public String getTimeExpire() {
		return timeExpire;
	}

	public void setTimeExpire(String timeExpire) {
		this.timeExpire = timeExpire;
	}

	public String getGoodsTag() {
		return goodsTag;
	}

	public void setGoodsTag(String goodsTag) {
		this.goodsTag = goodsTag;
	}

	public String getProductId() {
		return productId;
	}

	public void setProductId(String productId) {
		this.productId = productId;
	}
}
